package net.lulihu.pangolin.headless.client.handler;

import io.netty.buffer.ByteBuf;
import io.netty.channel.Channel;
import io.netty.channel.ChannelHandlerContext;
import io.netty.channel.ChannelOption;
import io.netty.channel.SimpleChannelInboundHandler;
import lombok.extern.slf4j.Slf4j;
import net.lulihu.pangolin.headless.client.component.ClientNetworkComponent;
import net.lulihu.pangolin.headless.common.protocol.ProtocolMessage;
import net.lulihu.pangolin.headless.common.protocol.ProtocolMessageType;
import net.lulihu.pangolin.headless.common.util.ChannelTwoWayBindKit;

/**
 * 真实服务数据处理程序
 */
@Slf4j
public class RealServerDataHandler extends SimpleChannelInboundHandler<ByteBuf> {

    @Override
    protected void channelRead0(ChannelHandlerContext ctx, ByteBuf buf) {
        Channel realChannel = ctx.channel();
        Channel proxyChannel = ChannelTwoWayBindKit.getBindChannel(realChannel);
        if (proxyChannel == null) {
            realChannel.close();
        } else {
            byte[] bytes = new byte[buf.readableBytes()];
            buf.readBytes(bytes);
            // 发送代理数据
            ProtocolMessage message = new ProtocolMessage();
            message.setType(ProtocolMessageType.TYPE_DATA_TRANSFER);
            message.setBody(bytes);
            proxyChannel.writeAndFlush(message);
        }
    }

    @Override
    public void channelWritabilityChanged(ChannelHandlerContext ctx) {
        Channel realChannel = ctx.channel();
        Channel proxyChannel = ChannelTwoWayBindKit.getBindChannel(realChannel);

        if (proxyChannel != null) {
            proxyChannel.config().setOption(ChannelOption.AUTO_READ, realChannel.isWritable());
        }
    }

    @Override
    public void channelInactive(ChannelHandlerContext ctx) {
        Channel realChannel = ctx.channel();
        Channel proxyChannel = ChannelTwoWayBindKit.getBindChannel(realChannel);

        if (proxyChannel != null && proxyChannel.isActive()) {
            // 告诉服务端通道断开
            ProtocolMessage message = new ProtocolMessage();
            message.setType(ProtocolMessageType.TYPE_DISCONNECT);
            proxyChannel.writeAndFlush(message);
            proxyChannel.close();
        }

        // 解除绑定
        ChannelTwoWayBindKit.unbind(proxyChannel, realChannel);
    }

    @Override
    public void exceptionCaught(ChannelHandlerContext ctx, Throwable cause) throws Exception {
        super.exceptionCaught(ctx, cause);
    }
}
